// 8085Object.cpp: implementation of the C8085Object class.
//
//////////////////////////////////////////////////////////////////////

#include "stdafx.h"
#include "8085.h"
#include "8085Object.h"
#include "SevenSegment.h"
#include "ComPort.h"
#include "Printer.h"

// if compiling with some other compiler or compiling in some other
// operating system the 'GUI_AVAILABLE' variable will atleast make
// sure that the C8085Object is independent of GUI.
#if defined GUI_AVAILABLE
#include "MyNumericBox.h"
#endif

#define CharToNum(x)      ((x>='0' && x<='9') ? x-'0' : \
                            (toupper(x)>'A') ? x -'A' + 10: x - 'a' + 10)
#define NumToChar(x)      ((x>=0 && x<=9) ? x+'0' : x - 10 + 'A' )


#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////

C8085Object::C8085Object() : CInstructionSet()
{
    Init();
}

C8085Object::~C8085Object()
{

}

///////////////////////////////////////////////////////////////
//
void C8085Object::Init()
{
	int i=0;
    for(i=0 ; i<m_nNumberOfInstructions; i++)
    {
        m_aInstructionSet[i].Execute = (runTimeFunction)m_aInstructions[i].r;
        m_aInstructionSet[i].Display = (displayFunction)m_aInstructions[i].d;
    }

    for(i=0; i<sizeof(m_Ports)/sizeof(m_Ports[0]) ; i++)
        m_Ports[i] = 0;
	m_nInstructionsPerSegment = MEM_SIZE/SEGMENTS;
    m_aSegments[0]=0;
    // no need to generate debug infor unless user specifies
    m_bGenDebugInfo = FALSE;    
    ResetMachine();
}

///////////////////////////////////////////////////////////////
//
void C8085Object::SetStartIP(word ip)
{
    m_StartIP = ip;
}

///////////////////////////////////////////////////////////////
//

void C8085Object::InsertMachineCode(word addr,byte b)
{
    WriteMem(addr,b);
}

void C8085Object::InsertMachineCode(word addr,byte opCode, word operand)
{
    WriteMem(addr,opCode);
    WriteMem(addr+1,operand);
}

void C8085Object::InsertMachineCode(word addr,byte opCode, byte operand)
{
    WriteMem(addr,opCode);
    WriteMem(addr+1,operand);
}

///////////////////////////////////////////////////////////////
// do regData = regData+data and set appropriate flags 
byte C8085Object::InternalAdd(byte regData,byte data,BOOL bSetCarry)
{
    byte b=((regData&0xf)+(data&0xf))&0x10;
    int temp2 = regData+data;
    regData = regData+data;

    SetSign(regData & 0x80);
    SetZero(regData==0);
    SetAuxCarry(b);

    if(bSetCarry) SetCarry(temp2>0xff);
    SetParityFlag(regData);
    //SetParity(regData&(regData-1));
    return regData;
}

///////////////////////////////////////////////////////////////
//
void C8085Object::ResetMachine()
{
   // initialize the LEDs to display '1 2 3 .. ' etc 
    int x[]={6,59,47,102,109,125,7,127};
	int i=0;
    for(i=0; i<NUM_OF_LEDS ; i++)
        SetLedData(i,x[i]);
	SetLedDataModified();
    SetStartIP(00);
    SetIP(00);
    SetSP(0xffee);
    SetPSW('0');
    SetSign(1);
    SetZero(0);
    SetParity(0);
    SetAuxCarry(0);
    SetCarry(0);
    for(i=0; i<MEM_SIZE ; i++) 
        mem[i] = 0;
    SetA(0);
    SetB(0);
    SetC(0);
    SetD(0);
    m_nCallStackDepth = 0;
    SetExceptionOnRet(FALSE);
	m_nSaveCallStackDepth=-1;
}

void C8085Object::SetFlagsAfterLogicalInstruction()
{
    // SetZero(!GetA());
    SetSign(GetA()&0x80);
    SetParityFlag(GetA());
    SetCarry(0);    // carry flag is reset 
    //SetAuxCarry(1); // auxillary carry flag is set 
}

void C8085Object::SetFlagsAfterLogicalInstruction(byte b)
{
    //SetZero(b);
    SetSign(b&0x80);
    SetParityFlag(b);
    SetCarry(0);    // carry flag is reset 
    //SetAuxCarry(1); // auxillary carry flag is set 
}

inline void C8085Object::InternalPush(word w)
{
    WriteMem(GetSP(),w);
    SetSP(GetSP()-2);
}

//simulate one instruction
void C8085Object::SimulateOneInstruction()
{
    m_Opcode = ReadMemByte(GetIP());
    /* some instructions like jmp,ret return 0 so that they can
        set the value of IP themselves
    */
    if(Execute(m_Opcode))  
        SetIP(GetIP()+GetInstructionLen(m_Opcode));
}

void C8085Object::StartMachine()
{
    SetIP(m_StartIP);
	RefreshSegments();
}

char * C8085Object::OpcodeToString(word addr,char *szPrefix)
{
    byte opcode = ReadMemByte(addr);  
    if(m_aInstructionSet[opcode].Display)
    {
        sprintf(m_szTemporary,"%s%s",m_aInstructionSet[opcode].displayStr,
        (this->*m_aInstructionSet[opcode].Display)(addr+1,szPrefix));
        return m_szTemporary;
    }
    else return m_aInstructionSet[opcode].displayStr;
}


///////////////////////////////////////////////////////////////
// Runtime implementation of the 8085 insructions

int  C8085Object::VKNop()
{
    return 1;
}

int  C8085Object::VKAci()
{
    byte b= ReadMemByte(GetIP()+1);
    SetA(InternalAdd(GetA(),b));
    return 1;
}

int  C8085Object::VKAdc()
{
    switch(m_Opcode)
    {
    case 0x88   :    SetA(InternalAdd(GetA(),GetB()+GetCarry()));break;
    case 0x89   :    SetA(InternalAdd(GetA(),GetC()+GetCarry()));break;
    case 0x8A   :    SetA(InternalAdd(GetA(),GetD()+GetCarry()));break;
    case 0x8B   :    SetA(InternalAdd(GetA(),GetE()+GetCarry()));break;
    case 0x8C   :    SetA(InternalAdd(GetA(),GetH()+GetCarry()));break;
    case 0x8D   :    SetA(InternalAdd(GetA(),GetL()+GetCarry()));break;
    case 0x8E   :    SetM(InternalAdd(GetA(),GetM()+GetCarry()));break;
    case 0x8F   :    SetA(InternalAdd(GetA(),GetA()+GetCarry()));break;
    }
    return 1;
}

int  C8085Object::VKAdd()
{
    switch(m_Opcode)
    {
    case 0x80   :    SetA(InternalAdd(GetA(),GetB()));break;
    case 0x81   :    SetA(InternalAdd(GetA(),GetC()));break;
    case 0x82   :    SetA(InternalAdd(GetA(),GetD()));break;
    case 0x83   :    SetA(InternalAdd(GetA(),GetE()));break;
    case 0x84   :    SetA(InternalAdd(GetA(),GetH()));break;
    case 0x85   :    SetA(InternalAdd(GetA(),GetL()));break;
    case 0x86   :    SetM(InternalAdd(GetA(),GetM()));break;
    case 0x87   :    SetA(InternalAdd(GetA(),GetA()));break;
    }
    return 1;
}

int  C8085Object::VKAdi()
{
    byte number = ReadMemByte(GetIP()+1);
    SetA(InternalAdd(GetA(),number));
    return 1;
}


int  C8085Object::VKAna()
{
    switch(m_Opcode)
    {
    case 0xA0   :   SetA(GetA()&GetB()); break;
    case 0xA1   :   SetA(GetA()&GetC()); break;
    case 0xA2   :   SetA(GetA()&GetD()); break;
    case 0xA3   :   SetA(GetA()&GetE()); break;
    case 0xA4   :   SetA(GetA()&GetH()); break;
    case 0xA5   :   SetA(GetA()&GetL()); break;
    case 0xA6   :   SetA(GetA()&GetM()); break;
    case 0xA7   :   SetA(GetA()&GetA()); break;
    }
    SetFlagsAfterLogicalInstruction();
    SetCarry(0);
    SetAuxCarry(1);
    return 1;
}

int  C8085Object::VKAni()
{
    byte b = ReadMemByte(GetIP()+1);
    SetA(GetA()&b);
    SetFlagsAfterLogicalInstruction();
    SetCarry(0);
    SetAuxCarry(1);
    return 1;
}

int  C8085Object::VKCall()
{
    word addr;
    addr = ReadMemWord(GetIP()+1); // address to jump to 

    switch(m_Opcode)
    {
    case 0xcd   :   if(addr==SYSTEM_CALL)  
                    {
                        PerformSystemCall();
                        return 1;
                    }
                    break;
        // call on carry 
    case 0xdc   :   if(!GetCarry()) return 1; break;
        // call on no carry 
    case 0xd4   :   if(GetCarry()) return 1; break;
        // call on positive - sign flag is 0 
    case 0xf4   :   if(GetSign()) return 1; break;
        // call on minus sign flag is 1 
    case 0xfc   :   if(!GetSign()) return 1; break;
        // call on parity even - parity falg is 1 
    case 0xec   :   if(!GetParity()) return 1; break;
        // call on parity odd 
    case 0xe4   :   if(GetParity()) return 1; break;
        // call on zero - zero flag is 1
    case 0xcc   :   if(!GetZero()) return 1; break;
        // call on no zero
    case 0xc4   :   if(GetZero()) return 1; break;
        // normal call 
    }
    IncrementStackDepth();
    
    SetSP(GetSP()-2);           // decrement SP first
    // save the address of the next instruction
    WriteMem(GetSP(),word(GetIP()+3));  
    SetIP(addr);
    return 0; 
    /* return '0' indicating the value of IP has been set
       and no need to set it from the calle function 
    */
}

inline int  C8085Object::VKCc()
{ // call on carry 
    return VKCall();
}

inline int  C8085Object::VKCnc()
{ // call on no carry 
    return VKCall();
}

inline int  C8085Object::VKCp()
{ // call on positive 
    return VKCall();
}

inline int  C8085Object::VKCm()
{ // call on minus
    return VKCall();
}

inline int  C8085Object::VKCpe()
{ // call on parity even 
    return VKCall();
}

inline int  C8085Object::VKCpo()
{ // call on parity odd 
    return VKCall();
}

inline int  C8085Object::VKCz()
{ // call on zero  
    return VKCall();
}

inline int  C8085Object::VKCnz()
{ // call on not zero 
    return VKCall();
}


inline int  C8085Object::VKCma()
{ 
    SetA(~GetA());
    return 1;
}

inline int  C8085Object::VKCmc()
{ 
    SetCarry(~GetCarry());
    return 1;
}

int  C8085Object::VKCmp()
{
    // The contents of the operand(reg or memory) are compared with the 
    // contents of the accumlator.  Both contents are preserved and the comparison
    // is shown by the settin the flags as follows

    // if(A) < : Carry flag is set and zero flag is reset.
    // if(A) = : zero flag is set and carry flag is reset.
    // if(A) > : cary and zero flags are reset.
    byte data;

    switch(m_Opcode)
    {
    case 0xb8   :   data = GetB(); break;
    case 0xb9   :   data = GetC(); break;
    case 0xba   :   data = GetD(); break;
    case 0xbb   :   data = GetE(); break;
    case 0xbc   :   data = GetH(); break;
    case 0xbd   :   data = GetL(); break;
    case 0xbe   :   data = GetM(); break;
    case 0xbf   :   data = GetA(); break;
    }
    data = ~data +1;  // take 2's complement
    InternalAdd(GetA(),data,1);
    return 1;
}

int  C8085Object::VKCpi()
{
    // The contents of the 8 bit immediate data are compared with the 
    // contents of the accumlator.  Both contents are preserved and the comparison
    // is shown by the settin the flags as follows

    // if(A) < : Carry flag is set and zero flag is reset.
    // if(A) = : zero flag is set and carry flag is reset.
    // if(A) > : cary and zero flags are reset.
    byte data = ~(ReadMemByte(GetIP()+1))+1;
    InternalAdd(GetA(),data,1);
    return 1;

    if(GetA()<data)
    {
        //SetFlagsAfterLogicalInstruction(GetA()-data);
        //InternalAdd(GetA()-data);
        SetCarry(1);
        SetZero(0);
    }
    else if(GetA()==data)
    {
        //SetFlagsAfterLogicalInstruction(GetA()-data);
        SetCarry(0);
        SetZero(1);
    }
    else
    {
        //SetFlagsAfterLogicalInstruction(GetA()-data);
        SetCarry(0);
        SetZero(0);
    }
    return 1;
}

int  C8085Object::VKDaa()
{
    // The contents of the accumulator are changed from a binary value to two
    // 4-bit binary-coded decimal(BCD) digits.  This is the only instructin
    // that uses the auxiliary flag(internally) to perform the binary-to-BCD
    // conversion
    // 1.   if the valud of the low-order four bits(D3-D0) in the acc is greater than 
    //      9 or if AC flag is set the andd 6 to the low order four bits.
    // 2.   if the value of the hiht-order four bits(D7-D4) in the ACC is greater than 9
    //      or if the Carry flag is set add 6(60) to high order four bits
    byte b = GetA();

    if(((b&0xf)>9) || GetAuxCarry()) b += 6;
    if(((GetA()>>4)>9) || GetCarry()) b += 60;
    SetA(b);
    SetFlagsAfterLogicalInstruction();
    return 1;
}

int  C8085Object::VKDad()
{
    // Add register Pair to H and L Registers
    // if result is greate ahtn 16 bits the CY flag is set.
    
    word data;

    switch(m_Opcode)
    {
    case 0x09       :   data = GetBC(); break;
    case 0x19       :   data = GetDE(); break;
    case 0x29       :   data = GetHL(); break;
    case 0x39       :   data = GetSP(); break;
    }

    int x = GetHL()+data;

    if(x>0xffff) SetCarry(1);
    SetHL(x&0xffff);
    return 1;
}

int  C8085Object::VKDcr()
{
    // The contents of the designated register/mem is decremented by 1 and the 
    // result stored in the same place.
    // S,Z,P,AC are modified.  CY is not modified
    switch(m_Opcode)
    {
    case 0x05       :   SetB(InternalAdd(GetB(),0xff,FALSE)); break;
    case 0x0D       :   SetC(InternalAdd(GetC(),0xff,FALSE)); break;
    case 0x15       :   SetD(InternalAdd(GetD(),0xff,FALSE)); break;
    case 0x1D       :   SetE(InternalAdd(GetE(),0xff,FALSE)); break;
    case 0x25       :   SetH(InternalAdd(GetH(),0xff,FALSE)); break;
    case 0x2D       :   SetL(InternalAdd(GetL(),0xff,FALSE)); break;
    case 0x35       :   
        {
            byte b = GetM();
            SetM(InternalAdd(b,0xff,FALSE)); 
            break;
        }
    case 0x3D       :   SetA(InternalAdd(GetA(),0xff,FALSE)); break;
    }
    return 1;
}

int  C8085Object::VKDcx()
{
    // The contents of the register pair are decremented by 1
    // No flags are affected.
    switch(m_Opcode)
    {
    case 0x0B       :   SetBC(GetBC()-1); break;
    case 0x1B       :   SetDE(GetDE()-1); break;
    case 0x2B       :   SetHL(GetHL()-1); break;
    case 0x3B       :   SetSP(GetSP()-1); break;
    }
    return 1;
}


int  C8085Object::VKDi()
{
    //ThrowException(severe,instruction_not_implemented,"Instruction not implemented");
    return 1;
}

int  C8085Object::VKEi()
{
    //ThrowException(severe,instruction_not_implemented,"Instruction not implemented");
    return 1;
}

///////////////////////////////////////////////////////////////
inline int  C8085Object::VKHlt()
{ 
    ThrowException(noerror,hlt_executed," Halt executed");
    return 1;
}

int  C8085Object::VKIn()
{
    byte addr= ReadMemByte(GetIP()+1);
    SetA(ReadPort(addr));
    return 1;
}

int  C8085Object::VKInr()
{
    // Increment reg/mem by 1
    // S,Z,P,AC are modifed. CY is not modified.
    switch(m_Opcode)
    {
    case 0x04       :   SetB(InternalAdd(GetB(),1,FALSE)); break;
    case 0x0C       :   SetC(InternalAdd(GetC(),1,FALSE)); break;
    case 0x14       :   SetD(InternalAdd(GetD(),1,FALSE)); break;
    case 0x1C       :   SetE(InternalAdd(GetE(),1,FALSE)); break;
    case 0x24       :   SetH(InternalAdd(GetH(),1,FALSE)); break;
    case 0x2C       :   SetL(InternalAdd(GetL(),1,FALSE)); break;
    case 0x34       :   
        {
            byte b = GetM();
            SetM(InternalAdd(b,1,FALSE)); break;
        }
    case 0x3C       :   SetA(InternalAdd(GetA(),1,FALSE)); break;
    }
    return 1;
}

int  C8085Object::VKInx()
{
    // The contents of the register pair are incremented by 1
    // No flags are affected.
    switch(m_Opcode)
    {
    case 0x0B       :   SetBC(GetBC()+1); break;
    case 0x1B       :   SetDE(GetDE()+1); break;
    case 0x2B       :   SetHL(GetHL()+1); break;
    case 0x3B       :   SetSP(GetSP()+1); break;
    }
    return 1;
}

int  C8085Object::VKJmp()
{
    switch(m_Opcode)
    {
    case 0xc3   :   break;
        // jump on carry 
    case 0xda   :   if(!GetCarry()) return 1; break;
        // jump on no carry 
    case 0xd2   :   if(GetCarry()) return 1; break;
        // jump on positive - sign flag is 0 
    case 0xf2   :   if(GetSign()) return 1; break;
        // jump on minus sign flag is 1 
    case 0xfa   :   if(!GetSign()) return 1; break;
        // jump on parity even - parity falg is 1 
    case 0xea   :   if(!GetParity()) return 1; break;
        // jump on parity odd 
    case 0xe2   :   if(GetParity()) return 1; break;
        // jump on zero - zero flag is 1
    case 0xca   :   if(!GetZero()) return 1; break;
        // jump on no zero
    case 0xc2   :   if(GetZero()) return 1; break;
    }
    word addr = ReadMemWord(GetIP()+1); // address to jump to 
    SetIP(addr);
    return 0; 
    /* return '0' indicating the value of IP has been set
       and no need to set it from the calle function 
    */
}


inline int  C8085Object::VKJc()
{ // Jmp on carry 
    return VKJmp();
}

inline int  C8085Object::VKJnc()
{ // Jmp on no carry 
    return VKJmp();
}

inline int  C8085Object::VKJp()
{ // Jmp on positive 
    return VKJmp();
}

inline int  C8085Object::VKJm()
{ // Jmp on minus
    return VKJmp();
}

inline int  C8085Object::VKJpe()
{ // Jmp on parity even 
    return VKJmp();
}

inline int  C8085Object::VKJpo()
{ // Jmp on parity odd 
    return VKJmp();
}

inline int  C8085Object::VKJz()
{ // Jmp on zero  
    return VKJmp();
}

inline int  C8085Object::VKJnz()
{ // Jmp on not zero 
    return VKJmp();
}

inline int  C8085Object::VKLda()
{ 
    // The contents of a memory location, specified by a 16-bit address
    // in the operand are copied to the accumulator.
    SetA(ReadMemByte(ReadMemWord(GetIP()+1)));
    return 1;
}

inline int  C8085Object::VKLdax()
{ 
    // The contents of a memory location, specified by the reg pair
    // in the operand are copied to the accumulator.
    if(m_Opcode==0x0A)    SetA(ReadMemByte(GetBC()));
    else SetA(ReadMemByte(GetDE()));
    return 1;
}

int  C8085Object::VKLhld()
{ 
    // The instruction copies the contents of the memory location pointed out
    // by the 16-bit address in register L and copies the content of the next
    // memory location in register H.

    SetL(ReadMemByte(ReadMemWord(GetIP()+1)));
    SetH(ReadMemByte(ReadMemWord(GetIP()+2)));
    return 1;
}

int  C8085Object::VKLxi()
{ 
    // The instruction loads 16-bit data in the register pair designated
    // in the operand.
    switch(m_Opcode)
    {
    case 0x01       :   SetBC(ReadMemWord(GetIP()+1)); break;
    case 0x11       :   SetDE(ReadMemWord(GetIP()+1)); break;
    case 0x21       :   SetHL(ReadMemWord(GetIP()+1)); break;
    case 0x31       :   SetSP(ReadMemWord(GetIP()+1)); break;
    }
    return 1;
}

int C8085Object::VKMov()
{
    // This instruction copies the contents of the source register into
    // the destination register.
    byte data;
    switch(m_Opcode%8)
    {
    case 0  : data = GetB(); break;
    case 1  : data = GetC(); break;
    case 2  : data = GetD(); break;
    case 3  : data = GetE(); break;
    case 4  : data = GetH(); break;
    case 5  : data = GetL(); break;
    case 6  : data = GetM(); break;
    case 7  : data = GetA(); break;
    }

    switch(m_Opcode/8)
    {
    case 0x8  : SetB(data); break;
    case 0x9  : SetC(data); break;
    case 0xa  : SetD(data); break;
    case 0xb  : SetE(data); break;
    case 0xc  : SetH(data); break;
    case 0xd  : SetL(data); break;
    case 0xe  : SetM(data); break;
    case 0xf  : SetA(data); break;
    }
    return 1;
}


int C8085Object::VKMvi()
{
    // The 8 bit immediate data is stored in reg/mem
    // the destination register.
    byte data = ReadMemByte(GetIP()+1);
    switch(m_Opcode)
    {
    case 0x06  : SetB(data); break;
    case 0x0E  : SetC(data); break;
    case 0x16  : SetD(data); break;
    case 0x1E  : SetE(data); break;
    case 0x26  : SetH(data); break;
    case 0x2E  : SetL(data); break;
    case 0x36  : SetM(data); break;
    case 0x3E  : SetA(data); break;
    }
    return 1;
}

int C8085Object::VKOra()
{
    // The contents of the accumulator are logically ored with the operand
    //  Z,S,P are modified. AC and CY are reset.
    switch(m_Opcode)
    {
    case 0xB0   :   SetA(GetA()|GetB()); break;
    case 0xB1   :   SetA(GetA()|GetC()); break;
    case 0xB2   :   SetA(GetA()|GetD()); break;
    case 0xB3   :   SetA(GetA()|GetE()); break;
    case 0xB4   :   SetA(GetA()|GetH()); break;
    case 0xB5   :   SetA(GetA()|GetL()); break;
    case 0xB6   :   SetA(GetA()|GetM()); break;
    case 0xB7   :   SetA(GetA()|GetA()); break;
    }
    SetFlagsAfterLogicalInstruction();
    SetCarry(0);
    SetAuxCarry(0);
    return 1;
}

int C8085Object::VKOri()
{
    // The contents of the accumulator are logically ored with the 8 bit operand
    //  Z,S,P are modified. AC and CY are reset.
    byte b = ReadMemByte(GetIP()+1);
    SetA(GetA()|b);
    SetFlagsAfterLogicalInstruction();
    SetCarry(0);
    SetAuxCarry(0);
    return 1;
}

int  C8085Object::VKOut()
{
    byte addr = ReadMemByte(GetIP()+1);
    WritePort(addr,GetA());
    return 1;
}

int  C8085Object::VKPchl()
{
    // The contents of H and L are copied into the program counter.
    // The contents of H are Placed as high-order byte and of Las low-order byte.
    SetIP((GetH()<<8)+GetL());
    return 1;
}

int  C8085Object::VKPop()
{
    // The contents of memory location pointed out by SP are copied to the low order register
    // such as (C,E,L and flags) of the operand.  The stack pointer is incremented by 1 and the
    // contents of that memory location are copied to the high order reg(B,D,H,A) of the operand.
    // SP is again incremented.

    switch(m_Opcode)
    {
    case 0xC1   :   SetC(ReadMemByte(GetSP())); SetB(ReadMemByte(GetSP()+1)); SetSP(GetSP()+2); break;
    case 0xD1   :   SetE(ReadMemByte(GetSP())); SetD(ReadMemByte(GetSP()+1)); SetSP(GetSP()+2); break;
    case 0xE1   :   SetL(ReadMemByte(GetSP())); SetH(ReadMemByte(GetSP()+1)); SetSP(GetSP()+2); break;
    case 0xF1   :   SetPSW(ReadMemByte(GetSP())); SetA(ReadMemByte(GetSP()+1)); SetSP(GetSP()+2); break;
    }
        
    return 1;
}

int  C8085Object::VKPush()
{
    // The contents of the register pair designated in the operand are copied into
    // the stack in the following sequence.  the stack pointer register is decremented
    // and the contents of the high-order register(B,D,H,A) are copied into that
    // location.  The stack pointer register is decremented again and the contents of t
    // the low-order register (C,E,L,flags) are copied to that location.

    SetSP(GetSP()-1);
    switch(m_Opcode)
    {
    case 0xC5   :   
        WriteMem(GetSP(),GetB());
        SetSP(GetSP()-1);
        WriteMem(GetSP(),GetC());
        break;

    case 0xD5   :  
        WriteMem(GetSP(),GetD());
        SetSP(GetSP()-1);
        WriteMem(GetSP(),GetE());
        break;

    case 0xE5   :  
        WriteMem(GetSP(),GetH());
        SetSP(GetSP()-1);
        WriteMem(GetSP(),GetL());
        break;

    case 0xF5   :  
        WriteMem(GetSP(),GetA());
        SetSP(GetSP()-1);
        WriteMem(GetSP(),GetPSW());
        break;
    }
    return 1;
}

int  C8085Object::VKRal()
{
    // each binary bit of the acc is rotated left by one position through the
    // carry flag.  Bit D7 is placed in the carry flag and the carry flag
    // is placed in the least significant position D0.
    // S,Z,P,AC are not modified

    byte carry = GetCarry();
    SetCarry(GetA()&0x80);
    SetA((GetA()<<1)|carry);
    return 1;
}

int  C8085Object::VKRar()
{
    // each binary bit of the acc is rotated right by one position through the
    // carry flag.  Bit D0 is placed in the carry flag and the carry flag
    // is placed in the least significant position D7.
    // S,Z,P,AC are not modified

    byte carry = GetCarry();
    SetCarry(GetA()&0x1);
    SetA((GetA()>>1)|(carry<<7));
    return 1;
}

int  C8085Object::VKRlc()
{
    // each binary bit of the acc is rotated left by one position.  
    // Bit D7 is placed in the position of D0 as well as in the carry flag.
    // S,Z,P,AC are not modified

    byte msb = GetA()&0x80;
    SetCarry(msb);
    SetA((GetA()<<1)|(msb>>7));
    return 1;
}

int  C8085Object::VKRrc()
{
    // each binary bit of the acc is rotated right by one position.  
    // Bit D0 is placed in the position of D7 as well as in the carry flag.
    // S,Z,P,AC are not modified

    byte lsb = GetA()&0x1;
    SetCarry(lsb);
    SetA((GetA()>>1)|(lsb<<7));
    return 1;
}

int  C8085Object::VKRet()
{
    // The two byte from the top of the stack are copied into the program counter 

    switch(m_Opcode)
    {
    case 0xC9   :   break;
        // return  on carry 
    case 0xD8   :   if(!GetCarry()) return 1; break;
        // return  on no carry 
    case 0xD0   :   if(GetCarry()) return 1; break;
        // return  on positive - sign flag is 0 
    case 0xF0   :   if(GetSign()) return 1; break;
        // return  on minus sign flag is 1 
    case 0xF8   :   if(!GetSign()) return 1; break;
        // return  on parity even - parity falg is 1 
    case 0xE8   :   if(!GetParity()) return 1; break;
        // return  on parity odd 
    case 0xE0   :   if(GetParity()) return 1; break;
        // return  on zero - zero flag is 1
    case 0xC8   :   if(!GetZero()) return 1; break;
        // return  on no zero
    case 0xC0   :   if(GetZero()) return 1; break;
    }
    
    SetIP(ReadMemWord(GetSP()));
    SetSP(GetSP()+2);
    if(m_bExceptionOnRet && GetStackDepth()>0 
		&& m_nSaveCallStackDepth==GetStackDepth())
	{
		m_nSaveCallStackDepth = -1;	// reset it
        ThrowException(noerror,ret_executed,"  ");
	}
    DecrementStackDepth();
    return 0;  // indicate that IP has been modified 
}

inline int  C8085Object::VKRc()
{ // return on carry 
    return VKRet();
}

inline int  C8085Object::VKRnc()
{ // return on no carry 
    return VKRet();
}

inline int  C8085Object::VKRp()
{ // return on positive 
    return VKRet();
}

inline int  C8085Object::VKRm()
{ // return on minus
    return VKRet();
}

inline int  C8085Object::VKRpe()
{ // return on parity even 
    return VKRet();
}

inline int  C8085Object::VKRpo()
{ // return on parity odd 
    return VKRet();
}

inline int  C8085Object::VKRz()
{ // return on zero  
    return VKRet();
}

inline int  C8085Object::VKRnz()
{ // return on not zero 
    return VKRet();
}

inline int  C8085Object::VKRim()
{ 
    // read interrupt mask
    //ThrowException(severe,instruction_not_implemented,"Instruction not implemented");
    return 1;
}

int  C8085Object::VKRst()
{
    // The RST instructions are equivalent to 1-byte call instructions to one
    // of the eight memory locations on page 0.
    
    word addr;

    switch(m_Opcode)
    {
        // rst 0
    case 0xC7   :   addr = 0x0000 ; break;
        // rst 1
    case 0xCF   :   addr = 0x0008 ; break;
        // rst 2
    case 0xD7   :   addr = 0x0010 ; break;
        // rst 3
    case 0xDF   :   addr = 0x0018 ; break;
        // rst 4
    case 0xE7   :   addr = 0x0020 ; break;
        // rst 5
    case 0xEF   :   addr = 0x0028 ; break;
        // rst 6
    case 0xF7   :   addr = 0x0030 ; break;
        // rst 7
    case 0xFF   :   addr = 0x0038 ; break;
    }
    InternalPush(GetIP());
    SetIP(addr);
    return 0;
    /* return '0' indicating the value of IP has been set
       and no need to set it from the calle function 
    */
}

int  C8085Object::VKSbb()
{
    // the contents of the operand and the borrow flag are subtracted from the
    // contents of the accumulator and the resuls are placed in the
    // accumulator.
    // All flags are modified

    byte b;
    // add with two's complement of (reg/mem+borrow)
    switch(m_Opcode)
    {
    case 0x98   :   b = ~(GetB()+GetCarry())+1;  break;
    case 0x99   :   b = ~(GetC()+GetCarry())+1;  break;
    case 0x9A   :   b = ~(GetD()+GetCarry())+1;  break;
    case 0x9B   :   b = ~(GetE()+GetCarry())+1;  break;
    case 0x9C   :   b = ~(GetH()+GetCarry())+1;  break;
    case 0x9D   :   b = ~(GetL()+GetCarry())+1;  break;
    case 0x9E   :   b = ~(GetM()+GetCarry())+1;  break;
    case 0x9F   :   b = ~(GetA()+GetCarry())+1;  break;
    }

    SetCarry(0);
    SetA(InternalAdd(GetA(),b));
    SetCarry(!GetCarry());
    return 1;
}

int  C8085Object::VKSbi()
{
    // the contents of the 8 bit operand and the borrow flag are subtracted from the
    // contents of the accumulator and the resuls are placed in the
    // accumulator.
    // All flags are modified

    byte b = ReadMemByte(GetIP()+1)+GetCarry();
    b = ~b+1; // 2's complement
    SetA(InternalAdd(GetA(),b));
    SetCarry(!GetCarry());
    return 1;
}

int  C8085Object::VKShld()
{
    // The contents of register L are stored in the memory location 
    // specified by the 16-bit address in the operand, and the contents of H
    // register are stored in the next memory location by increment the operand.
    // the contents of register HL  are not altered.  This is a 3 byte instruction.

    word addr = ReadMemWord(GetIP()+1);
    WriteMem(addr,GetL());
    WriteMem(addr+1,GetH());
    return 1;
}

int  C8085Object::VKSim()
{ 
    // Set interrupt mask
    //ThrowException(severe,instruction_not_implemented,"Instruction not implemented");
    return 1;
}

int  C8085Object::VKSphl()
{ 
    // copy H and L Regs to the Stack Pointer.  
    // The contents of the H register provide the hith-order address,
    // and contents of the L register provide the low-order address.
    SetSP(GetHL());
    return 1;
}

int  C8085Object::VKSta()
{ 
    // Store Accumulator Direct
    WriteMem(ReadMemWord(GetIP()+1),GetA());
    return 1;
}

int  C8085Object::VKStax()
{ 
    // Store Accumulator indirect
    WriteMem(ReadMemWord(GetIP()+1),GetA());
    return 1;
}

int  C8085Object::VKStc()
{ 
    // Set carry to 1
    SetCarry(1);
    return 1;
}

int  C8085Object::VKSub()
{
    // subtract reg or mem from acc
    // all flags are affected

    byte data;
    switch(m_Opcode)
    {
    case 0x90   :    data=GetB();break;
    case 0x91   :    data=GetC();break;
    case 0x92   :    data=GetD();break;
    case 0x93   :    data=GetE();break;
    case 0x94   :    data=GetH();break;
    case 0x95   :    data=GetL();break;
    case 0x96   :    data=GetM();break;
    case 0x97   :    data=GetA();break;
    }
    // get the 2's complement
    data = ~data+1;
    SetA(InternalAdd(GetA(),data));
    SetCarry(!GetCarry());
    return 1;
}

int  C8085Object::VKSui()
{
    // subtract 8 bit data acc
    // all flags are affected
    byte data = ReadMemByte(GetIP()+1);
    // get the 2's complement
    data = ~data+1;
    SetA(InternalAdd(GetA(),data));
    SetCarry(!GetCarry());
    return 1;
}

int  C8085Object::VKXchg()
{
    // Exchange H and L with D and E
    word data = GetHL();
    SetHL(GetDE());
    SetDE(data);
    return 1;
}

int C8085Object::VKXra()
{
    // The contents of the accumulator are logically ored with the operand
    //  Z,S,P are modified. AC and CY are reset.
    switch(m_Opcode)
    {
    case 0xA8   :   SetA(GetA()^GetB()); break;
    case 0xA9   :   SetA(GetA()^GetC()); break;
    case 0xAA   :   SetA(GetA()^GetD()); break;
    case 0xAB   :   SetA(GetA()^GetE()); break;
    case 0xAC   :   SetA(GetA()^GetH()); break;
    case 0xAD   :   SetA(GetA()^GetL()); break;
    case 0xAE   :   SetA(GetA()^GetM()); break;
    case 0xAF   :   SetA(GetA()^GetA()); break;
    }
    SetFlagsAfterLogicalInstruction();
    SetCarry(0);
    SetAuxCarry(0);
	SetZero(!GetA());
    return 1;
}

int C8085Object::VKXri()
{
    // The contents of the accumulator are logically ored with the 8 bit operand
    //  Z,S,P are modified. AC and CY are reset.

    byte b = ReadMemByte(GetIP()+1);
    SetA(GetA()^b);
    SetFlagsAfterLogicalInstruction();
    SetCarry(0);
    SetAuxCarry(0);
    return 1;
}

int  C8085Object::VKXthl()
{
    // Exchange H and L with top of stack
    word data = ReadMemWord(GetSP());
    WriteMem(GetSP(),GetHL());
    SetHL(data);
    return 1;
}

int  C8085Object::VKInvalid()
{
    ThrowException(severe,illegal_instruction,"Illegal Instruction ");
    return 1;
}

int  C8085Object::VKBreakPoint()
{
    ThrowException(noerror,breakpoint,"Breakpoint ");
    return 1;
}

void C8085Object::RefreshSegments(int startSegment,int numberOfSegments)
{
	word nextAddress;

	// expect a bug here 
    nextAddress = m_aSegments[startSegment-1];
	int i=0;
	for(i=startSegment; i<numberOfSegments; i++)
	{
		for(int j=0; j<GetInstrPerSeg(); j++)
		{
			//Search(ReadMemByte(nextAddress));
			nextAddress += GetInstructionLenAt(nextAddress);
            if(nextAddress>MEM_SIZE) goto doRest;
		}
		m_aSegments[i]=nextAddress;
	}
doRest:
    for( ; i<numberOfSegments ; i++)
        m_aSegments[i] = word(MEM_SIZE);
}

inline int C8085Object::GetInstrPerSeg()
{
	return m_nInstructionsPerSegment;
}

int C8085Object::WhichSegment(word addr)
{
	// in which segment is the given addr
	// optimize, use binary search
	int i=0;
	for(i=1; i<SEGMENTS ; i++)
		if((addr<=m_aSegments[i]) && (addr>m_aSegments[i-1])) return i;
	return i;
}

// return the starting address for the segment
word C8085Object::GetEndAddrInSegment(unsigned segment)
{
    return m_aSegments[segment%SEGMENTS];
}

// use this function to adjust segment boundaries.  
// A self modifying program can cause changes in segment boundaries
void C8085Object::AdjustSegment(word addr)
{
    int nSegment = WhichSegment(addr);
    if(addr==0 || nSegment==1) return;

    word prevSegAddr = GetEndAddrInSegment(nSegment-1);
    if(prevSegAddr==addr) RefreshSegments(nSegment-1,1);
    else RefreshSegments(nSegment,1);
}

word C8085Object::GetMemSize()
{
    return word(MEM_SIZE);
}

char * C8085Object::DisplayByte(word addr,char *szPrefix)
{
    static char str[16];
    sprintf(str,"%s%.2x",szPrefix,ReadMemByte(addr));
    return str;
}

char * C8085Object::DisplayWord(word addr,char *szPrefix)
{
    static char str[16];
    sprintf(str,"%s%.4x",szPrefix,ReadMemWord(addr));
    return str;
}


CString
C8085Object::GetErrorPrefix()
{
    CString t;
    t.Format("IP = %d -  ",GetIP());
    if(::nDebugPrefix)
        t =" C8085Object" + t; 
    return t;
}

void C8085Object::SetParityFlag(byte data)
{
    int nCount=0;
    for(; data ; data=data>>1)
        if(data&1) ++nCount;
    SetParity( (nCount+1)%2);
}

int C8085Object::GetLedData(int nIndex)
{
    return m_aLedData[nIndex];
}

void C8085Object::SetLedData(int nIndex, int nData)
{
    m_aLedData[nIndex] = nData;
}

void C8085Object::SetStatusLed(int nLed,int nData)
{
    //status,addr,data
	ASSERT(nLed<2);
    m_aLedData[nLed] = nData;
}
void C8085Object::SetAddressLed(int nLed,int nData)
{
    //status,addr,data
	ASSERT(nLed<4);
    m_aLedData[nLed+2] = nData;
}

void C8085Object::SetDataLed(int nLed,int nData)
{
    //status,addr,data
	ASSERT(nLed<2);
    m_aLedData[nLed+6] = nData;
}

void C8085Object::BlankAllLeds()
{
	int i=0;
	for(i=0; i<2 ; i++)
		SetStatusLed(i,0);
	for(i=0; i<4 ; i++)
		SetAddressLed(i,0);
	for(i=0; i<2 ; i++)
		SetDataLed(i,0);
}

int C8085Object::BadSystemCall()
{
    ThrowException(severe,bad_system_call," Bad System Call ");
    return 0;
}

void C8085Object::SetExceptionOnRet(BOOL bFlag)
{
    m_bExceptionOnRet = bFlag;
	m_nSaveCallStackDepth = GetStackDepth();
}

int C8085Object::PerformSystemCall()
{
    //BlankAllLeds();
    if(CMy8085App::IsIntelSDK())
    {
		try {
			DoIntelSDKCalls();
		}
		catch ( CMyException& e ) {
			ThrowException( e.GetSeverity( ), e.GetException( ), e.GetErrorMessage( ) );
		}
        return 1;
    }
	return 0;
}

void C8085Object::DoIntelSDKCalls()
{
    switch(GetA())
    {
    case    0:  
        _SystemReset();
		break;
    case    1:  
        _SystemBlankDisplay();
		SetLedDataModified();
		break;
	case	2:  
		_SystemDisplayDot();
		SetLedDataModified();
		break;
	case	3:  
		_SystemDisplayData();
		SetLedDataModified();
		break;
     case  4    :  
         _SystemDisplayErr();
         SetLedDataModified();
         break;
     case  5    :  
         _SystemReadFromKeyboard();
         break;
     case  6    :   
         _SystemCodeConversion();
         break;
     case  7    :   
         _SystemLengthOfBlock();
         break;
     case  8    :   
         _SystemGenerateTone();
         break;
     case  9    :   
         _SystemDelay();
         break;
     case  0xa  :   
         1;    /* this has not been implemented */
         break;
     case  0xb  :   
         _SystemDisplayHLData();
         SetLedDataModified();
         break;
     case  0xc  :   
         _SystemGetDataFromKeyboard();
         break;
     case  0xd  :   
         _SystemDisplayDataUsingMemoryPointer();
         SetLedDataModified();
         break;
     case  0xe  :   
         _SystemSerialInput();
         break;
     case  0xf  :   
         _SystemSerialOutput();
         break;
     case  0x10 :   
         _SystemPrintData();
         break;
     case  0x11 :   
         _SystemPrintCRLF();
         break;
	default:
	    BadSystemCall();
    }
}


// resets the system.  In my implementation it does nothing
void C8085Object::_SystemReset()
{

}

void C8085Object::_SystemBlankDisplay()
{
	int i;
	switch(GetC())
	{
	 case   0    :       
		 for(i=0; i<4 ; i++)
			SetAddressLed(i,0);
		 break;
	 case   1    :   
		 for(i=0; i<2 ; i++)
			SetDataLed(i,0);
		 break;
	 case   2    :
		 for(i=0; i<2 ; i++)
			SetStatusLed(i,0);
		 break;
	 case   3    :   
		 BlankAllLeds();
		 break;
	 default     :   
		 BadSystemCall();
	}
}


// status,address,data
void C8085Object::_SystemDisplayDot(void)
{
	switch(GetC())
	{
	 case  0   :   SetDataLed(1,LED_DOT);
				   break;
	 case  1   :   SetAddressLed(3,LED_DOT);
				   break;
	 case  2   :   SetAddressLed(2,LED_DOT);
				   SetAddressLed(3,LED_DOT);
				   break;
	 case  3   :   SetStatusLed(1,LED_DOT);
				   break;
	 default   :   BadSystemCall();
	}
}


void C8085Object::_SystemDisplayData(void)
{
	switch(GetC())
	{
		case  0   :   
			SetStatusLed(0,CSevenSegment::NumTo7Segment(ReadMemByte(GetHL())));
			break;
		case  1   :   
			SetStatusLed(1,CSevenSegment::NumTo7Segment(ReadMemByte(GetHL())));
			break;
		case  2   :   
			SetAddressLed(0,CSevenSegment::NumTo7Segment(ReadMemByte(GetHL())));
			break;
		case  3   :   
			SetAddressLed(1,CSevenSegment::NumTo7Segment(ReadMemByte(GetHL())));
			break;
		case  4   :   
			SetAddressLed(2, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL())));
			break;
		case  5   :   
			SetAddressLed(3, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL())));
			break;
		case  6   :   
			SetDataLed(0, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL())));
			break;
		case  7   :   
			SetDataLed(1, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL())));
			break;
		case  8   :   
			SetDataLed(0, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL())));
			SetDataLed(1, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL()+1)));
			break;
		case  9   :   
			SetAddressLed(0, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL())));
			SetAddressLed(1, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL()+1)));
			SetAddressLed(2, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL()+2)));
			SetAddressLed(3, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL()+3)));
		   break;
		case  0xA :   
			SetStatusLed(0, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL())));
			SetStatusLed(1, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL()+1)));
			break;
 		case  0xB :
			SetStatusLed(0, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL())));
			SetStatusLed(1, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL()+1)));
			SetAddressLed(0, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL()+2)));
			SetAddressLed(1, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL()+3)));
			SetAddressLed(2, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL()+4)));
			SetAddressLed(3, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL()+5)));
			SetDataLed(0, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL()+6)));
			SetDataLed(1, CSevenSegment::NumTo7Segment(ReadMemByte(GetHL()+7)));
			break;
		default   :   BadSystemCall();
	}
}

void C8085Object::SetLedDataModified(BOOL bModified)
{
	m_bLedDataModified = bModified;
}

BOOL C8085Object::IsLedDataModified()
{
	return m_bLedDataModified;
}

inline int C8085Object::NumTo7Segment(int x)
{
    return CSevenSegment::NumTo7Segment(x);
}

// display Err in the address field
void C8085Object::_SystemDisplayErr()
{
    BlankAllLeds();
	SetAddressLed(0, CSevenSegment::NumTo7Segment(0xE));
	SetAddressLed(1, DISPLAY_r);
	SetAddressLed(2, DISPLAY_r);
}
 
// read a key from keyboard and return the key code in the A register         
void C8085Object::_SystemReadFromKeyboard()
{
#if defined GUI_AVAILABLE
    CMyNumericBox c;
    static char str[32];
    static char szData[32];
    int nResult;

    sprintf(str,"Read a key from keyboard and return the key code in reg \'A\'");
    c.SetCaption(str);
    sprintf(szData,"0x%0.4x",GetA());
    
    if(c.ReadFromKeyboard(nResult,0,0xf,szData))
    {
        SetA((byte)nResult);
    }
#else
#error This requires a GUI interface to read from keyboard
#endif
}

void C8085Object::_SystemCodeConversion()
{
  // the idea behind this system call is not clear hence it is not properly implemented
  // converts HEX to ASCII & ASCII to HEX values When C=0 this function converts 
  // a hex value to its equivalent ASCII value.  This 8 bit hex data will be 
  // converted to 2 ASCII value
   switch(GetC())
   {
     case   0   :   
         // DE register pair will have the ASCII values D - Higher bytes, 
         // E Lower bytes
         SetD(NumToChar((GetL()>>4))); // get upper 4 bits 
         SetE(NumToChar((GetL()&0x0f))); // get lower 4 bits 
         break;
     case   1   :
         // H contains higher bytes ASCII valueI values L contains lower 
         // byte ASCII value A contains the hex value
         SetA( (CharToNum(GetH())<<4) +
             (CharToNum(GetL())&0x0f)); // get lower 4 bits 
         break;
     default    :   
         BadSystemCall();
   }
}

void C8085Object::_SystemLengthOfBlock(void)
{
   // this function calculates the length of a block of memory
   // i.e. find BC - HL
   //   if HL > BC, then a calculation error is displayed
   long x;

    if((x=GetBC()-GetHL())<0) _SystemDisplayErr();  //
    SetDE((word)x);
}

void C8085Object::_SystemGenerateTone(void)
{
   // generate tone for driving a speaker
   // but in our case we generate a tone for a short duration and quit
   switch(GetC())
   {
     case   0   :  // generate 1 KHZ 
         Beep(1000,75);
         break;
     case   1   :  // generate 2 KHZ 
         Beep(2000,75);
         break;
     default    :  
         BadSystemCall();
   }
}

void C8085Object::_SystemDelay(void)
{
    Sleep(7*GetHL());
}


void C8085Object::_SystemDisplayHLData()
{
   /* When 'c' = 0, contents of 'L' are displayed in the status field
      When 'c' = 1, contents of 'H' and 'L' are displayed in the
      address field.
      When 'c' = 2, contents of 'L' are displayed in the Data field
   */
   switch(GetC())
   {
     case 0x0     :  
         SetStatusLed(1,NumTo7Segment(GetL()&0x0f));
         SetStatusLed(0,NumTo7Segment((GetL()&0xf0)>>4));
         break;
     case 0x1     :  
         SetAddressLed(3,NumTo7Segment(GetL()&0x0f));
         SetAddressLed(2,NumTo7Segment((GetL()&0xf0)>>4));
         SetAddressLed(1,NumTo7Segment(GetH()&0x0f));
         SetAddressLed(0,NumTo7Segment((GetH()&0xf0)>>4));
         break;
     case 0x2     :  
         SetDataLed(1,NumTo7Segment(GetL()&0x0f));
         SetDataLed(0,NumTo7Segment((GetL()&0xf0)>>4));
         break;
     default      :  
         BadSystemCall();
   }
   //DisplayAllLeds();
}

void C8085Object::_SystemGetDataFromKeyboard()
{
#if defined GUI_AVAILABLE
    CMyNumericBox c;
    static char str[32];
    static char szData[32];
    int nResult;
    int i;

   /* When 'c'=0, input 4 keys, store as 16 bit data in 'HL' and
      display the data in address Led.
      When 'c'=1, input 2 keys, store as 8 bit data in 'L' and
      display data in data Led.
   */
   //HelpLine(DATA_FROM_KEYBOARD);
   switch(GetC())
   {
    case 0x0     :  
    sprintf(str,"Read 4 keys as 16 bit data into \'HL\' and display the data in address Led");
    c.SetCaption(str);
    sprintf(szData,"0x%0.4x",0);

    if(c.ReadFromKeyboard(nResult,0,0xffff,szData))
    {
        // last 2 bytes
        char str[256];
        _itoa(nResult,str,16);  // convert the number to string format
        ASSERT(strlen(str)<=4);
        // we expect at most 4 keys,  if less number of keys were
        // input then make the rest of number to 0
        for(i=strlen(str); i<4 ; i++)
            str[i]='0'; 
        SetH(CharToNum(str[3])<<4);
        SetH(GetH()|CharToNum(str[2]));
        SetAddressLed(0,NumTo7Segment(CharToNum(str[3])));
        SetAddressLed(1,NumTo7Segment(CharToNum(str[2])));

        SetL(CharToNum(str[1])<<4);
        SetL(GetL()|CharToNum(str[0]));
        SetAddressLed(2,NumTo7Segment(CharToNum(str[1])));
        SetAddressLed(3,NumTo7Segment(CharToNum(str[0])));
    }
    break;
    case 0x1     :  
    sprintf(str,"Read 2 keys as 8 bit data into \'L\' and display the data in data Led");
    c.SetCaption(str);
    sprintf(szData,"0x%0.4x",0);

    if(c.ReadFromKeyboard(nResult,0,0xff,szData))
    {
        // last 2 bytes
        char str[256];
        _itoa(nResult,str,16);  // convert the number to string format
        ASSERT(strlen(str)<=2);
        // we expect at most 4 keys,  if less number of keys were
        // input then make the rest of number to 0
        for(i=strlen(str); i<2 ; i++)
            str[i]='0'; 
        SetL(CharToNum(str[1])<<4);
        SetL(GetL()|CharToNum(str[0]));
        SetAddressLed(2,NumTo7Segment(CharToNum(str[1])));
        SetAddressLed(3,NumTo7Segment(CharToNum(str[0])));
    }
    break;
    default      :  
        BadSystemCall();
   }
#else
#error This requires a GUI interface to read from keyboard
#endif
}

void C8085Object::_SystemDisplayDataUsingMemoryPointer()
{
// display data using memory pointer
//      when c = 00, displays data in status field.
//           c = 01  displays data in address field.
//           c = 02  displays data in data field.
//           c = 03  displays data in all 8 digits.

    switch(GetC())
    {
		case  0   :  
			SetStatusLed(0,CSevenSegment::NumToSegment(ReadMemByte(GetHL())));
			SetStatusLed(1,CSevenSegment::NumToSegment(ReadMemByte(GetHL()+1)));
            break;
		case  1   :  
			SetAddressLed(0,CSevenSegment::NumToSegment(ReadMemByte(GetHL())));
			SetAddressLed(1,CSevenSegment::NumToSegment(ReadMemByte(GetHL()+1)));
			SetAddressLed(2,CSevenSegment::NumToSegment(ReadMemByte(GetHL()+2)));
			SetAddressLed(3,CSevenSegment::NumToSegment(ReadMemByte(GetHL()+3)));
			break;
		case   2   :  
			SetDataLed(0,CSevenSegment::NumToSegment(ReadMemByte(GetHL())));
			SetDataLed(1,CSevenSegment::NumToSegment(ReadMemByte(GetHL()+1)));
			break;
		case   3   :  
			SetStatusLed(0,CSevenSegment::NumToSegment(ReadMemByte(GetHL())));
			SetStatusLed(1,CSevenSegment::NumToSegment(ReadMemByte(GetHL()+1)));
			SetAddressLed(0,CSevenSegment::NumToSegment(ReadMemByte(GetHL()+2)));
			SetAddressLed(1,CSevenSegment::NumToSegment(ReadMemByte(GetHL()+3)));
			SetAddressLed(2,CSevenSegment::NumToSegment(ReadMemByte(GetHL()+4)));
			SetAddressLed(3,CSevenSegment::NumToSegment(ReadMemByte(GetHL()+5)));
			SetDataLed(0,CSevenSegment::NumToSegment(ReadMemByte(GetHL()+6)));
			SetDataLed(1,CSevenSegment::NumToSegment(ReadMemByte(GetHL()+7)));
			break;
		default    :  
			BadSystemCall();
			break;
    }
}

void C8085Object::_SystemSerialInput(void)
{
   // serial input data from COM1/COM2
   //   when c =0 serial input from com1 is stored in register 'B'
   //   when c =1 serial input from com2 is stored in register 'B'

    CComPort port; 
    switch(GetC())
    { 
    case 0:
        port.Open("COM1");
        SetB(port.Read());
        port.Close();
        break;
    case 1:   
        port.Open("COM2");
        SetB(port.Read());
        port.Close();
        break;
    default:   
        BadSystemCall();
   }
}

void C8085Object::_SystemSerialOutput(void)
{
   // serial input data from COM1/COM2
   // when c =0 data from register 'B' is sent to com1
   // when c =1 data from register 'B' is sent to com2

    CComPort port; 
    switch(GetC())
    { 
    case 0:
        port.Open("COM1");
        port.Write(GetB());
        port.Close();
        break;
    case 1:   
        port.Open("COM2");
        port.Write(GetB());
        port.Close();
        break;
    default:   
        BadSystemCall();
   }
}


void C8085Object::_SystemPrintData()
{
    CPrinter c;
    char str[32];

    switch(GetC())
    {
     case   0    :  str[0] = GetB();
                    str[1] = '\0';
                    break;
                    // print the ASCII format of B 
     case   1    :  sprintf(str,"%s",GetB());
                    break;
     default     :  BadSystemCall();
    }
    c.Write(str);
}

void C8085Object::_SystemPrintCRLF()
{
    CPrinter c;
    char str[32];

    // print a carriage return and linefeed 
    sprintf(str,"\r\n");
    c.Write(str);
}

///////////////////////////////////////////////////////////////
C8085Object::InstructionArray C8085Object::m_aInstructions[]=
{
{  (runTimeFunction)&(C8085Object::VKNop),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKLxi ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKStax),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInx ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKDcr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMvi ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKRlc ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKBreakPoint),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKDad ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKLdax),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKDcx ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKDcr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMvi ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKRrc ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInvalid),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKLxi ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKStax),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInx ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKDcr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMvi ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKRal ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInvalid),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKDad ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKLdax),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKDcx ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKDcr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMvi ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKRar ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKRim ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKLxi ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKShld),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKInx ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKDcr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMvi ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKDaa ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInvalid),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKDad ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKLhld),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKDcx ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKDcr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMvi ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKCma ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSim ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKLxi ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKSta ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKInx ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKDcr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMvi ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKStc ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInvalid),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKDad ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKLda ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKDcx ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKDcr ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMvi ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKCmc ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKHlt ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKMov ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdd ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdd ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdd ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdd ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdd ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdd ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdd ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdd ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdc ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdc ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdc ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdc ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdc ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdc ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdc ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdc ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSub ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSub ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSub ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSub ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSub ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSub ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSub ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSub ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSbb ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSbb ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSbb ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSbb ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSbb ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSbb ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSbb ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSbb ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAna ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAna ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAna ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAna ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAna ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAna ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAna ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAna ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKXra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKXra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKXra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKXra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKXra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKXra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKXra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKXra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKOra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKOra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKOra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKOra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKOra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKOra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKOra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKOra ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKCmp ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKCmp ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKCmp ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKCmp ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKCmp ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKCmp ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKCmp ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKCmp ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKRnz ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKPop ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKJnz ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKJmp ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKCnz ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKPush),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAdi ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKRst ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKRz  ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKRet ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKJz  ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKInvalid),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKCz  ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKCall),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKAci ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKRst ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKRnc ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKPop ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKJnc ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKOut ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKCnc ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKPush),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSui ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKRst ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKRc  ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKInvalid),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKJc  ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKIn  ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKCc  ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKInvalid),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKSbi ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKRst ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKRpo ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKPop ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKJpo ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKXthl),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKCpo ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKPush),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKAni ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKRst ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKRpe ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKPchl),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKJpe ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKXchg),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKCpe ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKInvalid),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKXri ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKRst ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKRp  ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKPop ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKJp  ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKDi  ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKCp  ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKPush),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKOri ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKRst ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKRm  ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKSphl),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKJm  ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKEi  ),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKCm  ),(displayFunction)&DisplayWord},
{  (runTimeFunction)&(C8085Object::VKInvalid),(displayFunction)NULL},
{  (runTimeFunction)&(C8085Object::VKCpi ),(displayFunction)&DisplayByte},
{  (runTimeFunction)&(C8085Object::VKRst ),(displayFunction)NULL}
};


